from typing import Optional, List, Dict
import pandas
import numpy
import json
import time
import copy
import zipfile

layers_depth: Any
materials_id: Any
materials: Any
profile_num: Any
water_depth: Any
profile_1d: Any

def find_node_by_id(id, node_set):
    ...

class Profile1D:
    """If top_elev is None,  it means there is no profile."""
    def __init__(self, top_elev: float = None, layers_depth: list = None, materials_id: list = None, materials: dict = None, profile_num = None, water_depth: float = None, x_coord: float = None, y_coord: float = None):
        ...
    @property
    def layers_thickness(self) -> Any:
        ...
    def cut_profile(self, cut_elev: float = 0.0, cut_above: bool = True, add_fill: bool = True, fill_id: int = ..., inplace = False) -> Optional[Any]:
        """
        This function is used to cut a profile to 2 profiles.
        
        Parameters:
        -----------
        cut_elev : float, default: 0.0
            The elevation at where to cut the profile.
        
        cut_above : bool, default: True
            If it's True, the profile above the cut_elev will be dropped.
        
        add_fill: bool, default: True
            If it's True, when the cut_elev is above the profile, fill will be added.
        
        fill_id : int, default: -1
            The material id for the fill.
        
        inplace : bool, default: False
            If it's true, the instance will be modified inplace, or a new instance will be returned.
        """
        ...
    def slice_profile(self, slice_top: float, slice_bottom: float, inplace = False):
        """
        This function is used to get(slice) a section of a profile between 2 elevations.
        If slice top is above profile top or slice bottom is below slice bottom, no fill will be added.
        """
        ...

class PreProfile1D(Profile1D):
    def __init__(self, top_elev: float = 0.0, uniform_nums: list = None, layers_depth: list = None, materials_id: list = None, materials: dict = None, profile_num = None, water_depth: float = None, x_coord: float = None, y_coord: float = None):
        ...
    def layer_consistency_check(self) -> list[dict]:
        """
        地层一致性检查，用于检查地层厚度、材料id的list是否具有相同的长度，如果长度不同，则说明某些地层没有赋属性，或者某些属性没有对应的地层
        return 错误日志（错误字典列表）
        """
        ...
    def layer_logic_check(self) -> list[dict]:
        """
        地层逻辑性检查，包括：1）地层编号是否缺失；2）主层层序是否发生倒转；3）地层深度未按照升序排列
        return 错误日志（错误字典列表）
        """
        ...
    def top_elev_exist(self) -> list[dict]:
        """
        检查钻孔孔顶标高是否存在
        return 错误字典列表
        """
        ...
    def kjf_to_preProSet(cls, kjf_file: str) -> list:
        """
        convert kjf file to PreProfile1D object list
        :param kjf_file: location of kjf file
        :return: PreProfile1D object list
        """
        ...
    def verticalbores_to_preProSet(cls, bores_table_para: Optional[Any] = None, layers_table_para: Optional[Any] = None, materials_name_para: Optional[Any] = None, use_layer_num: bool = True) -> List:
        """
        convert VerticalBores' tables to PreProfile1D object list
        :param bores_table_para: VerticalBores's initialize table
        :param layers_table_para: VerticalBores's initialize table
        :param materials_name_para: VerticalBores's initialize table
        :param use_layer_num:  using layerNum in uniforming process
        :return: PreProfile1D object list
        """
        ...

class UniProfile1D(Profile1D):
    def __init__(self, top_elev: float = 0.0, uniform_nums: list = None, layers_depth: list = None, materials_id: list = None, materials: dict = None, profile_num = None, water_depth: float = None, x_coord: float = None, y_coord: float = None):
        ...
    def from_evs_geo(cls, fp) -> list:
        """
        convert evs .geo file to list of PreProfile1D instance
        :param fp: open instance of geo file
        :return: list of PreProfile1D instance
        """
        ...
    def from_PreProfile1D(cls, preboring_set: list) -> list:
        """
        convert PreProfile1d instance to UniProfile1d instance
        :param preboring_set:PreProfile1D instance list
        :return: UniProfile1D instance list
        """
        ...
